<?php
namespace system\libraries\database;

/**
 * Database Table
 * 
 * @author Steffen Brem <steffenbrem@gmail.com>
 */
abstract class Table 
{
    /**
     * Table name
     * 
     * @var string
     */
    protected $_name;
    
    /**
     * Primary key
     * 
     * @var int
     */
    protected $_primary = 'id';
    
    
    /**
     * Stores an instance of the Database ActiveRecord
     * 
     * @var ActiveRecord
     */
    private $_ar;

    /**
     * Constructor
     * 
     * Stores an instance of the Database Adapter
     */
    public function __construct( $group = NULL )
    {
        $this->_ar = new ActiveRecord($group);
    }

    /**
     * Find a row from the table by it's primary key
     *  
     * @param int $primaryKey
     * @return mixed
     */
    public function find( $primaryKey )
    {
        $this->_ar->where($this->_primary, $primaryKey);
        return $this->_ar->get($this->_name)->row();
    }
    
    /**
     * Update a row in the table
     * 
     * Use the magic setter to set new values:
     * <pre>
     * $model->username = 'newUser';
     * $model->email    = 'newEmail';
     * $model->update(4);
     * </pre>
     * 
     * @param int $primaryKey
     */
    public function update( $primaryKey )
    {
        if ( $primaryKey )
        {
            $this->_ar->where($this->_primary, $primaryKey);
        }
        $this->_ar->update($this->_name);
    }
    
    /**
     * Insert data
     * 
     * Use the magic setter to set your data.
     * 
     * <pre>
     * $model->name = 'henk';
     * $model->age = 19;
     * $model->insert();
     * </pre>
     */
    public function insert()
    {
        $this->_ar->insert($this->_name);
    }
    
    /**
     * Get rows from table
     * 
     * By default, it will fetch all the columns and rows from the table. If you
     * want, you can specify which columns you want to fetch:
     * <pre>
     * $tableModel->get('name, email');
     * </pre>
     * 
     * If you want to order your results, give a second parameter which contains
     * the fieldnames and there order key (ASC or DESC).
     * 
     * <pre>
     * $tableModel->get('first_name, last_name', 
     * 'last_name DESC, first_name ASC');
     * </pre>
     * 
     * By default, all the results are ordered by the primary key ASC.
     * 
     * @return array
     */
    public function get( $columns = NULL, $order = 'ASC' )
    {
        $order = trim($order);

        // Check for column names and trim them
        if ( $columns )
        {
            $columns = $this->_explodeComma($columns);
            $this->_ar->select($columns);
        }
        
        // Handle the ORDER BY
        $valid = array('asc', 'ASC', 'desc', 'DESC');
        if ( in_array($order, $valid) )
        {
            $this->_ar->orderBy($this->_primary . ' ' . $order);
        }
        else
        {
            $order = $this->_explodeComma($order);
            foreach ( $order as $value )
            {
                $this->_ar->orderBy($value);
            }
        }
        
        return $this->_ar->get($this->_name)->result();
    }
    
    /**
     * Delete a row from the table
     * 
     * If you do not specify a parameter it will delete ALL the rows in your
     * table.
     * 
     * @param int $primaryKey
     */
    public function delete( $primaryKey = NULL )
    {
        if ( $primaryKey )
        {
            $this->_ar->where($this->_primary, $primaryKey);
            $this->_ar->delete($this->_name);
        }
        else
        {
            $this->_ar->delete($this->_name);
        }
    }
    
    /**
     * Count all rows of the table
     * 
     * @return int
     */
    public function total()
    {
        return $this->_ar->rowCount($this->_name);
    }
    
    /**
     * Returns the total affected rows
     *  
     * @return int
     */
    public function rowCount()
    {
        return $this->_ar->rowCount();
    }
    
    /**
     * Returns the insert Id
     * 
     * @return int
     */
    public function insertId()
    {
        return $this->_ar->insertId();
    }
    
    /**
     * Magic Setter
     * 
     * @param string $index
     * @param string $value
     */
    public function __set( $index, $value )
    {
        $this->_ar->set($index, $value);
    }
    
    /**
     * Explode an array by comma (,) and trim the values
     * 
     * @param array $array
     * @return array
     */
    private function _explodeComma( $array )
    {
        $array = explode(',', $array);
        foreach( $array as $key => $value )
        {
            $array[$key] = trim($value);
        }
        return $array;
    }
}

/* End of file Table.php */
